#!/bin/bash
#pMusic - read/write meta-tags (using ffmpeg)
#GPL - Copyright Sigmund Berglund

FILE="$1"

#read $3
if [ -f "$3" ]; then #$3 is used from func_index
	SUFFIX=func_index
	DB="$3" #let func_index use a temporary index so that pMusic can work normally during indexing, and because the user might want to cancel the indexing.
	DB_OUT="$4"
else
	SUFFIX="$(date +%s%N)" #unique suffix for every instance of func_id3io, rather than using MYPID from func_trackinfo which gives same suffix for different instances. --> SUFFIX=$3 #PID_GUI
	DB="$STORAGE_DIR/index_mymusic"
fi

update_gui (){
	#playlist
	IFS='|' read C1 C2 NAME C <<< "`grep -F "$FILE" $WORKDIR/playlist`"
	if [ "$NAME" ]; then
		( flock -e 201
			sed -i "s%|${NAME//&/\\&}|%|${NEW_NAME//&/\\&}|%g" $WORKDIR/playlist $WORKDIR/PLAYLIST_ALL
		) 201>$WORKDIR/playlist.lockfile 
	fi
	#update svg in main gui and now_playing file
	echo "|$FILE" > $HOME/.pmusic/nowplaying #this makes func_progressbar to activate full reading of playing track
	echo true > $WORKDIR/UPDATE_GUI
	#avoid updating of sourcelist for masstagger. func_id3tagger will do that after all tagging
	IFS='|' read C1 OLD_ARTIST OLD_TITLE C <<< "`grep -F "$FILE" $WORKDIR/sourcelist`"
	if [[ "$OLD_ARTIST" || "$OLD_TITLE" ]]; then
		SEARCH="$(tail -n1 "$STORAGE_DIR/index_history" | cut -d'|' -f3 | cut -c 5-)"
		case $SEARCH in
			*pMusic:\ Favorites*)	echo "$APPDIR/func_favorites -show_favorites" > $WORKDIR/exec_id3io_post;;
			*pMusic:*) 				echo "false" > $WORKDIR/exec_id3io_post;;
			*)						echo "$APPDIR/func -search_sources \"$SEARCH\"" > $WORKDIR/exec_id3io_post;;
		esac
	fi
	if [[ "$1" != *_no_update ]]; then
		$APPDIR/func_index -merge_stack &
		sleep 0.3  #because merge_stack runs in background and we reach here too quick
		chmod 722 $WORKDIR/exec_id3io_post
		$WORKDIR/exec_id3io_post
		echo -n > $WORKDIR/exec_id3io_post
		echo true > $WORKDIR/UPDATE_SOURCELIST
	fi
}

genre2human (){	#convert genre number to something human readable. See $APPDIR/txt_id3genre
	TMP="`echo "$1" | cut -d'(' -f2 | cut -d')' -f1`"
#	TMP=${$GENRE#*(}; TMP=${TMP%)*} #does it contain a number
	if [[ ${TMP} = ^[0-9]* ]]; then
		TMP=$((10#${TMP})) #remove leading 0
		GENRE="`grep -F "(${TMP})" $APPDIR/txt_id3genre`"
		GENRE=${GENRE%(*}
	else
		GENRE="$1"
	fi
	echo "$GENRE"
}

export -f update_gui genre2human



case "$2" in
-read*)
	#-read			(func_index)
	#-read_quick 	(func_progressbar)	Quick as possible - do not write to DB
	#-read_ffmpeg 	(func_trackinfo)	Ensure to read actual id3tags - things might have changed...
	IFS='|' read COMMAND ARTIST TITLE ALBUM NR YEAR GENRE COMMENT RATING FORMAT BITRATE LENGTH C13 ADR ICON DISC_ID ARTIST_ID LYRICS_ID ALBUMART_ID C20 TIMESTAMPS <<< "$(grep -Fam1 "${FILE}|" "$DB")"
	[ ! "$ICON" ] && case $FILE in *.pmu|*.m3u|*.pls) ICON='gtk-audio_playlist';; *) ICON='gtk-audio';; esac
	[ "$INPUT_MB_DISC_ID" ] && DISC_ID="$INPUT_MB_DISC_ID" #$INPUT_MB_DISC_ID - overwrite existing with specified. See trackinfo - album-tag
	[ "$LENGTH" ] && DB_INFO=true || DB_INFO=false #show scan-msg in main gui if false
	#skip complete read if info already in index. If call from func_trackinfo read anyway.
	if [[ "$LENGTH" && ${2} != '-read_ffmpeg' ]]; then 
		SKIP_DB_WRITE=true
	else
		if [[ "${FILE}" = @(*kar|*KAR|*mid|*MID) ]]; then
			TMP="`timidity -OuM8 -o $WORKDIR/tmp_midi.au "$SOURCE" | grep -F 'Playing time' | cut -d'~' -f2 | cut -d' ' -f1`" #seconds
			LENGTH=`$APPDIR/func_C -sec2time $TMP`
			FORMAT="midi"
			A=${FILE##*/}; ARTIST=${A% - *}
			T=${FILE##* - }; TITLE=${T%.*}
		else
			while read I; do
				case $I in
					*Duration:*)
						IFS=: read C1 H M S C <<< "${I%%.*}"
						M=$((10#$M)) #avoid octal
						[[ $H -gt 0 ]] && M=$(((10#$H * 60) + 10#$M))
						LENGTH=$(printf "%02d" $M):$(printf "%02d" $S)
						;;
					*Audio:*)
						IFS=: read C1 C2 C3 TMP C <<< "$I"
						IFS=' ' read FORMAT C2 C3 C4 C5 BITRATE C <<< "$TMP"
						FORMAT=${FORMAT/,/}
						;;
					*title*:*)	T=${I#*:}; TITLE=${T/ /};; #doing only TITLE=${I#*: } does not work when tag is set and is empty. - we have to do it in 2 operations
					*artist*:*)	A=${I#*:}; ARTIST=${A/ /};;
					*album*:*)	A=${I#*:}; ALBUM=${A/ /};;
					*year*:*)	Y=${I#*:}; YEAR=${Y/ /};;
					*comment*:*)C=${I#*:}; COMMENT=${C/ /};;
					*track*:*)	N=${I#*:}; NR=${N/ /};;
					*genre*:*)	G=${I#*:}; G=${G/ /}; GENRE="$(genre2human "$G")";;
					*Video:*)	ALBUMART=embedded;;
				esac
			done <<< "$(LC_ALL=C ffmpeg -i "$FILE" 2>&1)"
		fi
		ADR="$FILE"
		COMMAND="$FILE"
	fi
	#write to db if new info. -read_quick is used by func_progressbar while -read is used by func_index
	if [[ -f "$ADR" && "$2" != "-read_quick" && "$SKIP_DB_WRITE" != "true" ]]; then
		[ ! "$ARTIST" ] && ARTIST2="${ADR##*/}" || ARTIST2="$ARTIST" #Don't change $ARTIST - empty variable is used by func_trackinfo
		if [ "$SUFFIX" = "func_index" ]; then #no need to lock file since func_index is working with a copy of the db.
			echo "$COMMAND|$ARTIST2|$TITLE|$ALBUM|$NR|$YEAR|$GENRE|$COMMENT|$RATING|$FORMAT|$BITRATE|$LENGTH||$ADR|$ICON|$DISC_ID|$ARTIST_ID|$LYRICS_ID|$ALBUMART_ID||$TIMESTAMPS" >> $DB_OUT
		else
			( flock -e 202
				echo "$COMMAND|$ARTIST2|$TITLE|$ALBUM|$NR|$YEAR|$GENRE|$COMMENT|$RATING|$FORMAT|$BITRATE|$LENGTH||$ADR|$ICON|$DISC_ID|$ARTIST_ID|$LYRICS_ID|$ALBUMART_ID||$TIMESTAMPS" >> $WORKDIR/mymusic_stack
			) 202>$WORKDIR/mymusic_stack.lockfile 
		fi
	fi
	;;

-write*)
	A=${ARTIST/${TXT_SEARCH}.../};	ARTIST=${A/${TXT_NO_WWW}/}
	T=${TITLE/${TXT_SEARCH}.../};	TITLE=${T/${TXT_NO_WWW}/}
	A=${ALBUM/${TXT_SEARCH}.../};	ALBUM=${A/${TXT_NO_WWW}/}
	Y=${YEAR/${TXT_SEARCH}.../};	YEAR=${Y/${TXT_NO_WWW}/}
	N=${NR/${TXT_SEARCH}.../};		NR=${N/${TXT_NO_WWW}/}
	GENRE="$(genre2human "$GENRE")"
	#---
	echo "ffmpeg -i \"$FILE\" ${I_ALBUMART} -acodec copy -id3v2_version 3 -metadata title=\"$TITLE\" -metadata artist=\"$ARTIST\" -metadata album=\"$ALBUM\" -metadata year=\"$YEAR\" -metadata track=\"$NR\" -metadata comment=\"$COMMENT\" -metadata genre=\"$GENRE\" -y $WORKDIR/tmp_ffmpeg_copy_$SUFFIX.${FILE##*.}" > $WORKDIR/exec_id3io #echo to exec-file to optionally embed albumart to the audio file.
	chmod 722 $WORKDIR/exec_id3io
	$WORKDIR/exec_id3io
	#tag file if supported. Unsupported files gives an empty tmp-file
	if [ -s $WORKDIR/tmp_ffmpeg_copy_$SUFFIX.${FILE##*.} ]; then
		mv -f $WORKDIR/tmp_ffmpeg_copy_$SUFFIX.${FILE##*.} "$FILE"
		#update db
		( flock -e 202
			grep -aF "$FILE" "$STORAGE_DIR/index_mymusic" | awk -F'|' -v VAR1="$ARTIST" -v VAR2="$TITLE" -v VAR3="$ALBUM" -v VAR4="$NR" -v VAR5="$YEAR" -v VAR6="$GENRE" -v VAR7="$COMMENT" '{print $1 "|" VAR1 "|" VAR2 "|" VAR3 "|" VAR4 "|" VAR5 "|" VAR6 "|" VAR7 "|" $9 "|" $10 "|" $11 "|" $12 "|" $13 "|" $14 "|" $15 "|" $16 "|" $17 "|" $18 "|" $19 "|" $20 "|" $21}' >> $WORKDIR/mymusic_stack
		) 202>$WORKDIR/mymusic_stack.lockfile 
		#update gui
		if [[ "$TITLE" && "$ARTIST" ]]; then
			NEW_NAME="$ARTIST - $TITLE"
			update_gui "$2"
		fi
	fi
	;;

-clear*)
	ffmpeg -i "$FILE" -acodec copy -id3v2_version 3 -metadata title='' -metadata artist='' -metadata album='' -metadata year='' -metadata track='' -metadata comment='' -metadata genre='' -y $WORKDIR/tmp_ffmpeg_copy_$SUFFIX.${FILE##*.}
	mv -f $WORKDIR/tmp_ffmpeg_copy_$SUFFIX.${FILE##*.} "$FILE"

	#update db
	( flock -e 202
		grep -aF "$FILE" "$STORAGE_DIR/index_mymusic" | awk -F'|' '{print $1 "||||||||" $9 "|" $10 "|" $11 "|" $12 "|" $13 "|" $14 "|" $15 "|" $16 "|" $17 "|" $18 "|" $19 "|" $20 "|" $21}' >> $WORKDIR/mymusic_stack
	) 202>$WORKDIR/mymusic_stack.lockfile 
	#update gui
	NEW_NAME="${FILE##*/}"
	update_gui "$2"
	;;
esac
